/** ***********************************************************************************
* @file         battery_task.c
* @brief        备用电池充电管理任务
* @details      主要用来对锂电池进行充放电管理
* @author       杨小珛
* @date         2021/03/18
* @copyright    北京高知科技有限公司    
* @version      V1.0
* @attention    无
**************************************************************************************/
#include "lbs_task.h"
#include "mon_task.h"
#include "log_task.h"
#include "power_task.h"
#include "com_lib.h"
#include "gnss_task.h"
#include "net_port.h"
#include "rtc_task.h"
#include "cJSON.h"
#include "coor_trans.h"
#include "net_socket_api.h"
#include "flash_buffer.h"
#include "flash_config.h"
#include "ble_task.h"
#include "save_task.h"

#define LBS_STATA_IDLE  0x00
#define LBS_STATA_BUSY  0x01
static uint8_t g_LbsStata = LBS_STATA_IDLE;
static uint32_t g_LbsPositionMode = 0;


GaozSemaphoreHandle_t lbs_wifscan_read_msg_semaphore;
GaozQueueHandle_t lbs_wifscan_msg_queue;          /*HTTP 数据消息队列*/

static lbs_cellinfo_msg_t lbs_cellinfo_msg;     /*LBS 读取基站信息*/
static wifiscan_infor_msg_t wifiscan_infor_msg; /*WIFISCAN 读取信息*/  
static lbs_wifiscan_locating_infor_t lbs_wifiscan_locating_infor;
static lbs_wifiscan_key_infor_t lbs_wifiscan_key_infor;

static void lbs_wifiscan_handle_task( void * pvParameters );
static void lbs_wifscan_read_msg_semaphore_create(void);
static void lbs_wifscan_read_msg_semaphore_put( void );
static uint32_t lbs_wifscan_read_msg_semaphore_get( uint32_t timeout );

static void lbs_wifscan_msg_queue_create(void);
static uint32_t lbs_wifscan_msg_queue_get( lbs_wifscan_msg_typedef *msg , uint32_t time_out );
static uint32_t lbs_wifscan_msg_queue_set( lbs_wifscan_msg_typedef *msg );

static uint8_t lbs_get_mcc_mnc_from_plmn(uint8_t *plmn, uint8_t *mcc, uint8_t *mnc);
static void lbs_get_cellinfo_ex_cb( void *param );
//static void wifiscan_refponse_cb(void *param);
//static void http_response_handle_cb(void *pHttpParam, INT8 *data, INT32 len);
static uint32_t lbs_wifiscan_baiduyun_http_post_msg( char * post_data );
static uint32_t lbs_wifiscan_http_cjson_send_to_baiduyun(   uint8_t *key,               /*百度云账户SK*/
                                                uint8_t *imei,                          /*设备IMEI*/
                                                uint8_t *imsi,                          /*设备IMSI*/
                                                uint8_t *loc_ip,                        /*本地IP地址*/
                                                uint8_t *scellinfo,                     /*LBS信息 主基站*/
                                                uint8_t *ncellinfi,                     /*LBS信息 周边基站*/
                                                uint8_t *wifiscan_info,                 /*WIFI信息*/
                                                uint8_t *time );                        /*上报数据的时间*/  
static uint32_t lbs_wifiscan_http_cjson_recv_from_baiduyun( uint8_t *data, uint32_t len );

static uint32_t lbs_wifiscan_http_send_to_baiduyun( void );
static uint32_t lbs_wifiscan_infor_read( uint32_t mode );
/** ****************************************************************************
* @remarks       void lbs_wifiscan_man_create_task( unsigned portBASE_TYPE uxPriority )
* @brief         LBS\WIFISCAN 辅助定位数据信息管理
* @param[in]     uxPriority任务优先级；
* @param[out]    无
* @return        无
* @attention     在系统启动后进行创建
*******************************************************************************/
void lbs_wifiscan_man_create_task( unsigned portBASE_TYPE uxPriority )
{
    uint16_t aklen = LBS_WIFISCAN_KEY_LEN;
    uint8_t  akbuf[LBS_WIFISCAN_KEY_LEN] = { 0 };

    memset( (uint8_t *)&lbs_cellinfo_msg, 0x00, sizeof( lbs_cellinfo_msg_t ) );
    memset( (uint8_t *)&wifiscan_infor_msg, 0x00, sizeof( wifiscan_infor_msg_t ) );
    memset( (uint8_t *)&lbs_wifiscan_locating_infor, 0x00, sizeof( lbs_wifiscan_locating_infor_t ) );
    memset( (uint8_t *)&lbs_wifiscan_key_infor, 0x00, sizeof( lbs_wifiscan_key_infor_t ) );
    /*系统启动后读取FALSH中LBS AK信息*/
    if( save_lbs_key_read_form_flash( (uint8_t *)akbuf, (uint16_t *)&aklen ) == pdPASS )
    {
        lbs_wifiscan_key_infor.len = aklen;
        memcpy( (uint8_t *)lbs_wifiscan_key_infor.ak, (uint8_t *)akbuf, aklen );
        log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"LBS AK Flash parameter : len=%d,ak=%s",lbs_wifiscan_key_infor.len, lbs_wifiscan_key_infor.ak ); 
    }
    else
    {
    #if 1
        lbs_wifiscan_key_infor.len = strlen( (const char *)"bARC6JXhk2Jr0tdHjbSiNCu2pgUiZaaW");
        memcpy( (uint8_t *)lbs_wifiscan_key_infor.ak, ( const char *)"bARC6JXhk2Jr0tdHjbSiNCu2pgUiZaaW", lbs_wifiscan_key_infor.len );
        log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"LBS AK init parameter : len=%d,ak=%s",lbs_wifiscan_key_infor.len, lbs_wifiscan_key_infor.ak ); 
    #endif
    }
    lbs_wifscan_read_msg_semaphore_create();    /*创建 LBS WIFISCAN 数据处理信号量*/
    lbs_wifscan_msg_queue_create();               /*创建HTTP POST消息队列*/
    gaoz_thread_create(lbs_wifiscan_handle_task, LBS_MAN_NAME, 1024*16, NULL, uxPriority);
}

/** ****************************************************************************
* @remarks       void lbs_wifiscan_key_cfg_init( lbs_wifiscan_key_infor_t *key_cfg )
* @brief         初始化LBS KEY 配置参数
* @param[in]     *key_cfg 初始化数据
* @param[out]    无
* @return        无
* @attention     无
*******************************************************************************/
void lbs_wifiscan_key_cfg_init( lbs_wifiscan_key_infor_t *key_cfg )
{
    if(( key_cfg == NULL ) || ( &lbs_wifiscan_key_infor == key_cfg ))
    {
        return;
    }
    memcpy((uint8_t *)&lbs_wifiscan_key_infor, (const uint8_t *)key_cfg, sizeof(lbs_wifiscan_key_infor_t));
}

/** ****************************************************************************
* @remarks       static void lbs_wifscan_read_msg_semaphore_create(void)
* @brief         创建LBS WIFISCAN 信号量
* @param[in]     无
* @param[out]    无
* @return        无
* @attention     无
*******************************************************************************/
static void lbs_wifscan_read_msg_semaphore_create(void)
{
    lbs_wifscan_read_msg_semaphore = gaoz_sem_new(0);
    if( lbs_wifscan_read_msg_semaphore == 0 )
    {
        while( 1 ); /*创建失败,进行处理*/
    }
}

/** ****************************************************************************
* @remarks       static void uint32_t lbs_wifscan_read_msg_semaphore_put( void )
* @brief         发送LBS WIFISCAN 信号量信息
* @param[in]     无
* @param[out]    无
* @return        无
* @attention     必须在任务中运行
*******************************************************************************/
static void lbs_wifscan_read_msg_semaphore_put( void )
{
    if( lbs_wifscan_read_msg_semaphore == 0 )
    {
        lbs_wifscan_read_msg_semaphore_create();
    }
    gaoz_sem_signal( lbs_wifscan_read_msg_semaphore );
}

/** ****************************************************************************
* @remarks       static uint32_t lbs_wifscan_read_msg_semaphore_get( uint32_t timeout )
* @brief         获取LBS WIFISCAN 信号量信息
* @param[in]     timeout 超时时间
* @param[out]    无
* @return        pdPASS 接收到数据 pdFAIL 未接收到数据
* @attention     必须在任务中运行
*******************************************************************************/
static uint32_t lbs_wifscan_read_msg_semaphore_get( uint32_t timeout )
{
    uint32_t res = pdFAIL;
    
    if( lbs_wifscan_read_msg_semaphore == 0 )
    {
        lbs_wifscan_read_msg_semaphore_create();
    }
    if( gaoz_sem_try_wait( lbs_wifscan_read_msg_semaphore , timeout ) == pdPASS )
    {
        res = pdPASS;
    }
    
    return res;
}

/** ****************************************************************************
* @remarks       static void lbs_wifscan_msg_queue_create(void)
* @brief         创建http post 数据消息队列
* @param[in]     无
* @param[out]    无
* @return        无
* @attention     无
*******************************************************************************/
static void lbs_wifscan_msg_queue_create(void)
{
    /* 创建模块HTTP发送数据的消息队列 */
    lbs_wifscan_msg_queue = gaoz_queue_create( LBS_WIFISCAN_MSG_QUEUE_DEPTH, sizeof( lbs_wifscan_msg_typedef ) );
    if( lbs_wifscan_msg_queue == 0 )
    {
        while( 1 ); /*创建失败,进行处理*/
    }
}

/** ****************************************************************************
* @remarks       uint32_t lbs_wifscan_msg_queue_get(lbs_wifscan_msg_typedef *msg , uint32_t time_out )
* @brief         获取HTTP数据发送消息队列数据
* @param[in]     *http_msg 获取的数据地址
* @param[out]    无
* @return        pdPASS 接收到数据 pdFAIL 未接收到数据
* @attention     必须在任务中运行
*******************************************************************************/
static uint32_t lbs_wifscan_msg_queue_get( lbs_wifscan_msg_typedef *msg , uint32_t time_out )
{
    if( lbs_wifscan_msg_queue == 0 )
    {
        lbs_wifscan_msg_queue_create();
    }
    if( gaoz_queue_get( lbs_wifscan_msg_queue, msg, time_out )  == 0 ) //等待回应信号量
    {
        return pdPASS;
    }
    else
    {
        return pdFAIL;
    }
    
    return pdFAIL;
}

/** ****************************************************************************
* @remarks       static uint32_t lbs_wifscan_msg_queue_set( lbs_wifscan_msg_typedef *msg )
* @brief         发送HTTP数据发送消息队列数据
* @param[in]     *msg 数据源地址
* @param[out]    无
* @return        无
* @attention     无
*******************************************************************************/
static uint32_t lbs_wifscan_msg_queue_set( lbs_wifscan_msg_typedef *msg )
{   
    if( lbs_wifscan_msg_queue == 0 )
    {
        lbs_wifscan_msg_queue_create();
    }
    if( gaoz_queue_put( lbs_wifscan_msg_queue, msg , 100 ) == 0 )
    {
        return pdPASS;
    }
    else
    {
        return pdFAIL;
    }
    
    return pdFAIL;
}

/** ****************************************************************************
* @remarks       static uint8_t lbs_get_mcc_mnc_from_plmn(uint8_t *plmn, uint8_t *mcc, uint8_t *mnc)
* @brief         LBS辅助定位获取MCC MNC
* @param[in]     *plmn 数据源地址
* @param[out]    *mcc *mnc 数据输出目标地址
* @return        0 、2、3 使用官方demo 无解释
* @attention     无
*******************************************************************************/
static uint8_t lbs_get_mcc_mnc_from_plmn(uint8_t *plmn, uint8_t *mcc, uint8_t *mnc)
{
    if (plmn == NULL || mcc == NULL || mnc == NULL)
    {
        return 0;
    }
    //64 F0 10
    mcc[0] = plmn[0] & 0x0F;
    mcc[1] = plmn[0] >> 4;
    mcc[2] = plmn[1] & 0x0F;

    mnc[0] = plmn[2] & 0x0F;
    mnc[1] = plmn[2] >> 4;
    mnc[2] = plmn[1] >> 4;

    if (mnc[2] > 9)
    {
        mnc[2] = 0;
        return 2;
    }
    else
    {
        return 3;
    }
}

/** ****************************************************************************
* @remarks       uint8_t get_lbs_cellinfo( uint8_t * pu8LbsCellInfoData )
* @brief         获取LBS读取到的信息
* @param[in]     用于存储LBS信息的地址
* @param[out]    无
* @return        无
* @attention     无
*******************************************************************************/
 uint8_t get_lbs_cellinfo( uint8_t * pu8LbsCellInfoData )
 {
    uint8_t i = 0;
    uint16_t len = 0;
    uint8_t imei[NET_MOD_IMEI_LEN+2] = { 0 };
    uint8_t imsi[NET_MOD_IMSI_LEN+2] = { 0 };
    uint32_t timestamp;
    uint8_t lbs_new_state;

    lbs_new_state = gnss_lbs_position_new_state_get();

    log_debug_printf( DEBUG_MODE, LBS_MAN_NAME, "gnssInof.gnss_position_info.is_lbs_type = %d \r\n",lbs_new_state);
    if(lbs_new_state == LBS_ONLY_READ)
    {
        gnss_lbs_position_new_state_set(0);
        pu8LbsCellInfoData[len++] = 0x00;
    
        net_module_run_state_get( MOD_IMEI, imei );
        
        net_module_run_state_get( MOD_IMSI, imsi );

        memcpy(&pu8LbsCellInfoData[len],imei,15);
        log_debug_printf( DEBUG_MODE, LBS_MAN_NAME, "imei = %s \r\n",imei );
        len += 15;
        memcpy(&pu8LbsCellInfoData[len],imsi,15);
        log_debug_printf( DEBUG_MODE, LBS_MAN_NAME, "imsi = %s \r\n",imsi);
        len += 15;
        rtc_sys_get( RTC_TIM_TIMESTAMP, (uint32_t *)&timestamp );
        log_debug_printf( DEBUG_MODE, LBS_MAN_NAME, "time = %d \r\n",timestamp);
        u32toHex4(timestamp,&pu8LbsCellInfoData[len]);
        len += 4;

        /*主基站*/
        u16toHex2(lbs_cellinfo_msg.service.mcc,&pu8LbsCellInfoData[len]); 
        log_debug_printf( DEBUG_MODE, LBS_MAN_NAME, "lbs_cellinfo_msg.service.mcc = %d \r\n",lbs_cellinfo_msg.service.mcc);
        len += 2;
        pu8LbsCellInfoData[len] = lbs_cellinfo_msg.service.mnc;
        log_debug_printf( DEBUG_MODE, LBS_MAN_NAME, "lbs_cellinfo_msg.service.mnc = %d \r\n",lbs_cellinfo_msg.service.mnc);
        len += 1;
        u16toHex2(lbs_cellinfo_msg.service.lac,&pu8LbsCellInfoData[len]); 
        log_debug_printf( DEBUG_MODE, LBS_MAN_NAME, "lbs_cellinfo_msg.service.lac = %d \r\n",lbs_cellinfo_msg.service.lac);
        len += 2;
        u32toHex4(lbs_cellinfo_msg.service.cellid,&pu8LbsCellInfoData[len]); 
        log_debug_printf( DEBUG_MODE, LBS_MAN_NAME, "lbs_cellinfo_msg.service.cellid = %d \r\n",lbs_cellinfo_msg.service.cellid);
        len += 4;
        u16toHex2(lbs_cellinfo_msg.service.signal+140,&pu8LbsCellInfoData[len]); 
        log_debug_printf( DEBUG_MODE, LBS_MAN_NAME, "lbs_cellinfo_msg.service.signal = %d \r\n",lbs_cellinfo_msg.service.signal+140);
        len += 2;
        /* 辅助基站 */
        log_debug_printf( DEBUG_MODE, LBS_MAN_NAME, "lbs_cellinfo_msg.ncell_num = %d \r\n",lbs_cellinfo_msg.ncell_num);
        lbs_cellinfo_msg.ncell_num = lbs_cellinfo_msg.ncell_num > 5 ? 5 : lbs_cellinfo_msg.ncell_num;
        pu8LbsCellInfoData[len] = lbs_cellinfo_msg.ncell_num;
        len++;
        for(i=0; i<lbs_cellinfo_msg.ncell_num; i++)
        { 
            u16toHex2(lbs_cellinfo_msg.ncell[i].mcc,&pu8LbsCellInfoData[len]); 
            log_debug_printf( DEBUG_MODE, LBS_MAN_NAME, "lbs_cellinfo_msg.ncell[%d].mcc = %d \r\n",i,lbs_cellinfo_msg.ncell[i].mcc);
            len += 2;
            pu8LbsCellInfoData[len] = lbs_cellinfo_msg.ncell[i].mnc;
            log_debug_printf( DEBUG_MODE, LBS_MAN_NAME, "lbs_cellinfo_msg.ncell[%d].mnc = %d \r\n",i,lbs_cellinfo_msg.ncell[i].mnc);
            len += 1;
            u16toHex2(lbs_cellinfo_msg.ncell[i].lac,&pu8LbsCellInfoData[len]); 
            log_debug_printf( DEBUG_MODE, LBS_MAN_NAME, "lbs_cellinfo_msg.ncell[%d].lac = %d \r\n",i,lbs_cellinfo_msg.ncell[i].lac);
            len += 2;
            u32toHex4(lbs_cellinfo_msg.ncell[i].cellid,&pu8LbsCellInfoData[len]); 
            log_debug_printf( DEBUG_MODE, LBS_MAN_NAME, "lbs_cellinfo_msg.ncell[%d].cellid = %d \r\n",i,lbs_cellinfo_msg.ncell[i].cellid);
            len += 4;
            u16toHex2((lbs_cellinfo_msg.ncell[i].signal+140),&pu8LbsCellInfoData[len]); 
            log_debug_printf( DEBUG_MODE, LBS_MAN_NAME, "lbs_cellinfo_msg.ncell[%d].signal = %d \r\n",i,lbs_cellinfo_msg.ncell[i].signal+140);
            len += 2;
        }

        
    }

    log_debug_printf( DEBUG_MODE, LBS_MAN_NAME, "gnssInof.gnss_position_info.is_lbs_type len = %d \r\n",len);

    return len ;
 }

/** ****************************************************************************
* @remarks       void lbs_get_cellinfo_ex_cb( unsigned portBASE_TYPE uxPriority )
* @brief         LBS 回调函数
* @param[in]     *param 回调参数
* @param[out]    无
* @return        无
* @attention     无
*******************************************************************************/
static void lbs_get_cellinfo_ex_cb( void *param )
{
	uint8_t sMCC[3] = {0};
	uint8_t sMNC[3] = {0};

    if(param == NULL)
    {
        log_debug_printf( DEBUG_MODE, LBS_MAN_NAME, "cellinfo GET cellinfo FAIL\r\n" );
		return;
	}
    opencpu_cellinfo_t *cellinfo = (opencpu_cellinfo_t *)param;
    memset( (uint8_t *)&lbs_cellinfo_msg, 0x00, sizeof( lbs_cellinfo_msg_t ) );
	if( cellinfo->curr_rat >=4 )
	{
	    int cellid_s = cellinfo->lte_cellinfo.lteScell.enodeBID << 8 | cellinfo->lte_cellinfo.lteScell.cellId;
		lbs_get_mcc_mnc_from_plmn(&cellinfo->lte_cellinfo.lteScell.plmn[0], &sMCC[0], &sMNC[0]);
		//log_debug_printf( DEBUG_MODE, LBS_MAN_NAME, "cellinfo service MCC=%d%d%d,MNC=%d%d,CELL_ID = %lX,TAC=%X", sMCC[0],sMCC[1],sMCC[2],sMNC[0],sMNC[1],cellid_s,cellinfo->lte_cellinfo.lteScell.tac );
        lbs_cellinfo_msg.scell_num = 1;
        lbs_cellinfo_msg.service.mcc = sMCC[0]*100 + sMCC[1]*10 + sMCC[2];
        lbs_cellinfo_msg.service.mnc = sMNC[0]*10 + sMNC[1];
        lbs_cellinfo_msg.service.lac = cellinfo->lte_cellinfo.lteScell.tac;
        lbs_cellinfo_msg.service.cellid = cellid_s;
        lbs_cellinfo_msg.service.signal = cellinfo->lte_cellinfo.lteScell.rsrp - 140;
        log_debug_printf( DEBUG_MODE, LBS_MAN_NAME, "cellinfo service MCC=%d,MNC=%d,CELL_ID = %ld,TAC=%d,SIG=%d", 
                        lbs_cellinfo_msg.service.mcc,
                        lbs_cellinfo_msg.service.mnc,
                        lbs_cellinfo_msg.service.cellid,
                        lbs_cellinfo_msg.service.lac,
                        lbs_cellinfo_msg.service.signal );
        if( cellinfo->lte_cellinfo.lteNcellNum > 0 )
        {
            cellinfo->lte_cellinfo.lteNcellNum = cellinfo->lte_cellinfo.lteNcellNum > 5 ? 5 : cellinfo->lte_cellinfo.lteNcellNum;
            lbs_cellinfo_msg.ncell_num = cellinfo->lte_cellinfo.lteNcellNum;
            for( int i =0; i<cellinfo->lte_cellinfo.lteNcellNum;i++ )
            {
                memset(sMCC,0,3);
				memset(sMNC,0,3);
                int cellid_nb = cellinfo->lte_cellinfo.lteNcell[i].cellAccRelInfo.enodeBID << 8 | cellinfo->lte_cellinfo.lteNcell[0].cellAccRelInfo.cellId;
				lbs_get_mcc_mnc_from_plmn(&cellinfo->lte_cellinfo.lteNcell[i].cellAccRelInfo.plmn[0], &sMCC[0], &sMNC[0]);
				int tac = cellinfo->lte_cellinfo.lteNcell[i].cellAccRelInfo.tac;
			    //log_debug_printf( DEBUG_MODE, LBS_MAN_NAME, "cellinfo Ncell[%d]MCC=%d%d%d,MNC=%d%d, CELL ID = %lX,TAC=%X",i,sMCC[0],sMCC[1],sMCC[2],sMNC[0],sMNC[1],cellid_nb,tac );
                lbs_cellinfo_msg.ncell[i].mcc = sMCC[0]*100 + sMCC[1]*10 + sMCC[2];
                lbs_cellinfo_msg.ncell[i].mnc = sMNC[0]*10 + sMNC[1];
                lbs_cellinfo_msg.ncell[i].lac = tac;
                lbs_cellinfo_msg.ncell[i].cellid = cellid_nb;
                lbs_cellinfo_msg.ncell[i].signal = cellinfo->lte_cellinfo.lteNcell[i].rsrp  - 140;
                log_debug_printf( DEBUG_MODE, LBS_MAN_NAME, "cellinfo Ncell[%d]MCC=%d,MNC=%d, CELL ID = %ld,TAC=%d,SIG=%d",
                                i,
                                lbs_cellinfo_msg.ncell[i].mcc,
                                lbs_cellinfo_msg.ncell[i].mnc,
                                lbs_cellinfo_msg.ncell[i].cellid,
                                lbs_cellinfo_msg.ncell[i].lac,
                                lbs_cellinfo_msg.ncell[i].signal );
            }
        }
        lbs_wifscan_read_msg_semaphore_put(); /*数据读取成功，发送信号量通知任务程序*/
	}
	else
	{
	    lbs_get_mcc_mnc_from_plmn(&cellinfo->gsm_cellinfo.pCurrCellInfo.nTSM_LAI[0], &sMCC[0], &sMNC[0]);
		int cellid = cellinfo->gsm_cellinfo.pCurrCellInfo.nTSM_CellID[0]<<8|cellinfo->gsm_cellinfo.pCurrCellInfo.nTSM_CellID[1];
		int lac = cellinfo->gsm_cellinfo.pCurrCellInfo.nTSM_LAI[3]<<8|cellinfo->gsm_cellinfo.pCurrCellInfo.nTSM_LAI[4];
	    log_debug_printf( DEBUG_MODE, LBS_MAN_NAME, "cellinfo GSM service MCC=%d%d%d,MNC=%d%d,CELL_ID = %lX,TAC=%X",sMCC[0],sMCC[1],sMCC[2],sMNC[0],sMNC[1],cellid,lac );
        if( cellinfo->gsm_cellinfo.pNeighborCellInfo.nTSM_NebCellNUM>0)
		{
		    for(int i =0; i<cellinfo->gsm_cellinfo.pNeighborCellInfo.nTSM_NebCellNUM;i++)
		    {
				lbs_get_mcc_mnc_from_plmn(&cellinfo->gsm_cellinfo.pNeighborCellInfo.nTSM_NebCell[i].nTSM_LAI[0], &sMCC[0], &sMNC[0]);
				int cellid_n = cellinfo->gsm_cellinfo.pNeighborCellInfo.nTSM_NebCell[i].nTSM_CellID[0]<<8|cellinfo->gsm_cellinfo.pNeighborCellInfo.nTSM_NebCell[i].nTSM_CellID[1];
				int lac_n = cellinfo->gsm_cellinfo.pNeighborCellInfo.nTSM_NebCell[i].nTSM_LAI[3]<<8|cellinfo->gsm_cellinfo.pNeighborCellInfo.nTSM_NebCell[i].nTSM_LAI[4];
				log_debug_printf( DEBUG_MODE, LBS_MAN_NAME, "cellinfo GSM nbcell[%d] MCC=%d%d%d,MNC=%d%d,CELL_ID = %lX,TAC=%X", i,sMCC[0],sMCC[1],sMCC[2],sMNC[0],sMNC[1],cellid_n,lac_n );
            }
		}
        log_debug_printf( DEBUG_MODE, LBS_MAN_NAME, "cellinfo GET cellinfo for GSM cell info" );
	}
}

/** ****************************************************************************
* @remarks       static void wifiscan_refponse_cb(void *param)
* @brief         WIFI回调函数
* @param[in]     *param 回调参数
* @param[out]    无
* @return        无
* @attention     无
*******************************************************************************/
static void wifiscan_refponse_cb(void *param)
{
    uint32_t num = 0;

    if(param != NULL)
    {
		fibo_wifiscan_res_t *ap_info = (fibo_wifiscan_res_t *)param;
        memset( (uint8_t *)&wifiscan_infor_msg, 0x00, sizeof( wifiscan_infor_msg_t ) );
        log_debug_printf( DEBUG_MODE, LBS_MAN_NAME, "wifiscan ap_info->ap_num=%d",ap_info->ap_num );
        ap_info->ap_num = ap_info->ap_num>5?5:ap_info->ap_num;
        log_debug_printf( DEBUG_MODE, LBS_MAN_NAME, "-wifiscan ap_info->ap_num=%d",ap_info->ap_num );
        wifiscan_infor_msg.mac_num = ap_info->ap_num;
		if( ap_info->ap_num > 0 )
        {
            for( num = 0; num < ap_info->ap_num; num++ )
            {
                wifiscan_infor_msg.infor[num].ap_rssi = ap_info->fibo_wifiscan_ap_info[num].ap_rssi;
                memcpy( (uint8_t *)wifiscan_infor_msg.infor[num].ap_addr, ap_info->fibo_wifiscan_ap_info[num].ap_addr, WIFISCAN_AP_ADDR_MAX_LEN );
                log_debug_printf( DEBUG_MODE, LBS_MAN_NAME, "wifiscan ap_info[%d].rssi=%d",num,ap_info->fibo_wifiscan_ap_info[num].ap_rssi);
                log_debug_printf( DEBUG_MODE, LBS_MAN_NAME, "wifiscan ap_info[%d].addr=%s",num,ap_info->fibo_wifiscan_ap_info[num].ap_addr);
            }
            lbs_wifscan_read_msg_semaphore_put(); /*数据读取成功，发送信号量通知任务程序*/
        }
	}
	else 
	{
		log_debug_printf( DEBUG_MODE, LBS_MAN_NAME,"wifiscan fail");
	}
    fibo_wifiscan_off();
}

#if 0
/** ****************************************************************************
* @remarks       static void http_response_handle_cb(void *pHttpParam, INT8 *data, INT32 len)
* @brief         百度云HTTP数据回调函数
* @param[in]     *pHttpParam HTTP参数 *data 数据源地址 len 数据长度
* @param[out]    无
* @return        无
* @attention     无
*******************************************************************************/
static void http_response_handle_cb(void *pHttpParam, INT8 *data, INT32 len)
{
    gaoz_task_sleep(50);
    fibo_http_response_status_line((oc_http_param_t *)pHttpParam);
    log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"HTTP response code          : %d", ((oc_http_param_t *)pHttpParam)->respCode);
    log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"HTTP response version       : %s", ((oc_http_param_t *)pHttpParam)->respVersion);
    log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"HTTP response reason phrase : %s", ((oc_http_param_t *)pHttpParam)->respReasonPhrase);
    log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"HTTP Recive Data : %d %s", len, data);
    //http_post_msg_queue_set( (uint8_t *)data, len );
}

void cb_http_header_handle(const UINT8 *name, const UINT8 *value)
{
    log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"Header: %s : %s", name, value);
}
#endif

/** ****************************************************************************
* @remarks       static uint32_t lbs_wifiscan_baiduyun_http_post_msg( char * post_data )
* @brief         百度云HTTP数据发送
* @param[in]     * post_data 发送数据源地址
* @param[out]    无
* @return        pdPASS-成功  pdFAIL-失败
* @attention     无
*******************************************************************************/
static uint32_t lbs_wifiscan_baiduyun_http_post_msg( char * post_data )
{
#if 0
    #define HTTP_POST_MSG_WAIT_TIME ( 5000 )
    http_post_msg_typedef http_msg = { 0 };
    uint32_t ret = pdFAIL;
    uint32_t post_len = 0;
    char post_head[128]  = { 0 };
    const char *url = "http://api.map.baidu.com/locapi/v2"; /*百度云地址*/

    oc_http_param_t * pstHttpParam = NULL;
    
    if( post_data == NULL )
    {
        return pdFAIL;
    }
    post_len = strlen( (const char *)post_data );
    if(( post_len == 0 ) || ( post_len > 1024 ))
    {
        return pdFAIL;
    }
    log_debug_printf(DEBUG_MODE,LBS_MAN_NAME , "TEST - 1" );
    /*填充POST HEAD 消息体长度*/
    sprintf( post_head, "POST /locapi/v2 HTTP/1.1\r\nHost: api.map.baidu.com\r\nContent-Type: application/json\r\nContent-Length: %ld\r\n\r\n", post_len );
    /* http post */
    pstHttpParam = fibo_http_new();
    if(NULL == pstHttpParam)
    {
       return pdFAIL;
    }
    log_debug_printf(DEBUG_MODE,LBS_MAN_NAME , "TEST - 2" );
    /* prepare http get param */
    pstHttpParam->timeout = 30;
    pstHttpParam->cbReadBody = http_response_handle_cb;
    pstHttpParam->respCode = 500;
    pstHttpParam->bIsIpv6 = false;
    pstHttpParam->enHttpReadMethod = OC_USER_CALLBACK;
    memset(pstHttpParam->filepath, 0, OC_HTTP_FILE_PATH_LEN);
    //if(strlen(filepath) <= OC_HTTP_FILE_PATH_LEN)
    //{
    //    strncpy((char *)pstHttpParam->filepath, filepath, strlen(filepath));
    //}
    memset(pstHttpParam->url, 0, OC_HTTP_URL_LEN + 1);
    if(strlen((const char *)url) <= OC_HTTP_URL_LEN)
    {
        strncpy((char *)pstHttpParam->url, url, strlen(url));
    }
    else
    {
        fibo_http_delete(pstHttpParam);
        return pdFAIL;
    }
    log_debug_printf(DEBUG_MODE,LBS_MAN_NAME , "TEST - 3" );
    gaoz_task_sleep( 1000 );    /*延时1S钟等待稳定*/
    //The header file specified by HTTP post
    //The number of Content-Length in post_Head is Post_Data of Length
    //for ( ;; )
    {
        log_debug_printf(DEBUG_MODE,LBS_MAN_NAME , "fibo_http_post - SEND");
        if( fibo_http_post( pstHttpParam, (UINT8 *)post_data, (UINT8 *)post_head ) == 0 )
        {
            log_debug_printf(DEBUG_MODE,LBS_MAN_NAME , "fibo_http_post - OK");
        }
        else
        {   
            log_debug_printf(DEBUG_MODE,LBS_MAN_NAME , "fibo_http_post - ERROR");
        }
    }
    //fibo_http_post_ex(pstHttpParam, (UINT8 *)post_data, (UINT8 *)post_head, strlen(post_data));
    log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"HTTP response code          : %d", pstHttpParam->respCode);
    log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"HTTP response version       : %s", pstHttpParam->respVersion);
    log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"HTTP response reason phrase : %s", pstHttpParam->respReasonPhrase);
    log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"HTTP response body len      : %d", pstHttpParam->respContentLen);
    /*等待平台应答*/
    //gaoz_task_sleep( HTTP_POST_MSG_WAIT_TIME );    /*延时1S钟等待稳定*/
    fibo_http_response_header_foreach(pstHttpParam, cb_http_header_handle);
    if( OC_USER_CALLBACK == pstHttpParam->enHttpReadMethod )
    {
        log_debug_printf(DEBUG_MODE,LBS_MAN_NAME , "TEST - 6");
    }
    #if 0
    if( http_post_msg_queue_get( &http_msg , HTTP_POST_MSG_WAIT_TIME ) == pdPASS )
    {
        log_debug_printf(DEBUG_MODE,LBS_MAN_NAME , "TEST - 4" );
        if(( http_msg.data != NULL ) && ( http_msg.len != 0 ))
        {
            log_debug_printf(DEBUG_MODE,LBS_MAN_NAME , "TEST - 5" );
            ret = lbs_wifiscan_http_cjson_recv_from_baiduyun( http_msg.data, http_msg.len );
            gaoz_free_mem( (void *)http_msg.data );
        }
    }
    #endif
    log_debug_printf(DEBUG_MODE,LBS_MAN_NAME , "TEST - 7,RET = %d", ret);
    fibo_http_delete(pstHttpParam);
    pstHttpParam = NULL;
    return ret;
#else
 uint8_t key_safe_key[16] = { 0xBA,0xC3,0xC8,0xCB,0xBA,0xC3,0xB3,0xB5,0xB0,0xB2,0xC8,0xAB,0xC3,0xDC,0xD4,0xBF };
    #define BAIDUYUN_LBS_HOST   "test.zcloud.hrhaoche.com" /*百度云平台地址*/
    //  #define BAIDUYUN_LBS_HOST   "zcloud.hrhaoche.com" /*百度云平台地址*/
    #define BAUDUYUN_LBA_PORT   80                  /*百度云平台端口号*/
    #define POST_HEAD_LEN       2048                 /*请求头地址*/
    #define GET_DATA_LEN        1024                /*接收到的数据长度*/
    #define RECV_DATA_WAIT_TIME 10                   /*等待接收数据的时间*/
    uint32_t ret = pdFAIL, socketid = 0, post_len = 0,aes_buf_len = 0,aes_data_head_len = 0,aes_packet_num = 0;
    char *post_buf = NULL,*get_buf = NULL, *pjson = NULL,*aes_buf = NULL,*ase_ascii_buf = NULL,*decrypt_aes_buf = NULL;    
    int32_t get_len = 0;
    uint8_t recv_time = 0;
    fd_set readfds, errorfds, writeset ;
    struct timeval tv;

    if( post_data == NULL )
    {
        return pdFAIL;
    }
    post_len = strlen( (const char *)post_data );
    aes_buf_len = post_len; 
    if(( post_len == 0 ) || ( post_len > 1024 ))
    {
        return pdFAIL;
    }
 
    aes_buf = ( char *)gaoz_malloc_mem( aes_buf_len + POST_HEAD_LEN );

    if( aes_buf == NULL )
    {
        return pdFAIL;
    } 
    memset(aes_buf,0,aes_buf_len + POST_HEAD_LEN);

    //aes_data_head_len = sprintf( aes_buf, "Content-Type: application/json\r\nContent-Length: %ld\r\n\r\n", post_len );
    aes_data_head_len = 0;
    memcpy(&aes_buf[aes_data_head_len],post_data,aes_buf_len);//haorenhaoche_aes_test
    aes_buf_len += aes_data_head_len;
    aes_packet_num = aes_buf_len / 16;
    if((aes_buf_len%16) != 0)
    { 
       aes_packet_num++; 
    }
 
    aes_buf_len = aes_packet_num * 16;

    log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"aes_buf_len = %d aes_buf = %s", aes_buf_len ,aes_buf);
/*
    aes_encrypt_multi( (uint8_t *)aes_buf,aes_buf_len,key_safe_key);

    log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"aes_encrypt_multi aes_buf_len = %d aes_buf = %s", aes_buf_len ,aes_buf);

     
    aes_decrypt_multi((uint8_t *)aes_buf,aes_buf_len,key_safe_key);

    log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"aes_decrypt_multi aes_buf_len = %d aes_buf = %s", aes_buf_len ,aes_buf);
*/
    aes_encrypt_multi( (uint8_t *)aes_buf,aes_buf_len,key_safe_key);

    
    ase_ascii_buf = ( char *)gaoz_malloc_mem( aes_buf_len*2 + POST_HEAD_LEN );
    if( ase_ascii_buf == NULL )
    {
        return pdFAIL;
    } 
    memset(ase_ascii_buf,0,aes_buf_len*2 + POST_HEAD_LEN);
    aes_buf_len = HexToAsciiString((char *)ase_ascii_buf,( const char * )aes_buf, aes_buf_len);
    log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"aes_buf_len = %d ase_ascii_buf = %s", aes_buf_len ,ase_ascii_buf);


       post_buf = ( char *)gaoz_malloc_mem( post_len + POST_HEAD_LEN );
    if( post_buf == NULL )
    {
        return pdFAIL;
    }
    get_buf = ( char *)gaoz_malloc_mem( GET_DATA_LEN );
    if( get_buf == NULL )
    {
        return pdFAIL;
    } 
    memset( (uint8_t *)post_buf, 0x00, post_len + POST_HEAD_LEN );
    memset( (uint8_t *)get_buf, 0x00, GET_DATA_LEN );
    post_len = sprintf( post_buf, "POST /ota/baidu/lbs HTTP/1.1\r\nHost: test.zcloud.hrhaoche.com\r\nContent-Type: application/json\r\nContent-Length: %ld\r\n\r\n", aes_buf_len );
    //post_len = sprintf( post_buf, "POST /ota/baidu/lbs HTTP/1.1\r\nHost: test.zcloud.hrhaoche.com\r\n", 0 );
   


   log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"post_len = %d post_buf = %s", post_len ,post_buf);
    

    for(int i = 0; i<aes_buf_len; i++)
    {
        post_buf[post_len + i ] = ase_ascii_buf[i];  
    }
    post_len += aes_buf_len;
    log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"post_len = %d post_buf = %s", post_len ,post_buf);
        

    
    /*创建百度云网络连接**********************************************************************************************/
    if( socket_free_connect( BAIDUYUN_LBS_HOST, BAUDUYUN_LBA_PORT ,e_socket_protocol_tcp , &socketid ) == pdPASS )
    {
        log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"Baidu Cloud LBS server is successfully connected,socket id = %d", socketid );
        
        if( socket_free_write( socketid , ( uint8_t *)post_buf , post_len ) == pdPASS )
        {
            log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"Baidu Cloud Send Data : %d %s", post_len, post_buf );
            for( ;; )
            {
                FD_ZERO(&readfds);FD_ZERO(&errorfds);FD_ZERO(&writeset);
                FD_SET(socketid, &writeset);FD_SET(socketid, &readfds);FD_SET(socketid, &errorfds);
                tv.tv_sec  = 1; tv.tv_usec = 0;
                get_len = fibo_sock_lwip_select( socketid+1, &readfds, NULL, &errorfds, &tv );
                if( get_len == 0 )
                {
                    recv_time++;
                    if( recv_time >= RECV_DATA_WAIT_TIME )  /*等待3S后没有接收到数据直接退出等待*/
                    {
                        recv_time = 0; 
                        break;
                    }
                }
                else if( get_len < 0 )
                {
                    break;
                }
                else
                {
                    if(FD_ISSET(socketid, &errorfds))	
                    {
                    	break;
                    }
                    else if(FD_ISSET(socketid, &readfds))
                    {
                        get_len = socket_free_recv( socketid ,( uint8_t *)get_buf , GET_DATA_LEN );
                        if( get_len > 0 )
                        {
                            log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"Baidu Cloud Recive Data : %d %s", get_len, get_buf );
                            pjson = strchr( (const char *)get_buf, '{' );
                            if( pjson != NULL )
                            {
                                log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"Bif( pjson != NULL ) start --",0 );
                           
                                ret = lbs_wifiscan_http_cjson_recv_from_baiduyun( (uint8_t *)pjson, sizeof( (const char *)pjson ) );
                           
                                log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"Bif( pjson != NULL ) end --",0 );
                            }
                            log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"Bif( pjson == NULL ) ",0 );
                            break;
                        }
                        else
                        {
                            log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"Baidu Cloud Recive Data Error : %d", get_len );
                        }  
                    }  
                }  
            }       
        }
        socket_free_close( socketid , e_socket_protocol_tcp );
    }
    
    if(ase_ascii_buf != NULL)
    {
        gaoz_free_mem( (void *)ase_ascii_buf );
    }

    if(aes_buf != NULL)
    {
        gaoz_free_mem( (void *)aes_buf );
    }

    if( post_buf != NULL )
    {
        gaoz_free_mem( (void *)post_buf );
    }
    if( get_buf != NULL )
    {
        gaoz_free_mem( (void *)get_buf );
    }

    return ret;
#endif
}

/** ****************************************************************************
* @remarks       static void lbs_wifiscan_http_cjson_send( uint8_t *key, uint8_t imei, lbs_cellinfo_msg_t *lbs_info, wifiscan_infor_msg_t wifiscan_info )
* @brief         将LBS/WIFISCAN 数据进行CJSON格式转换，将数据发送到百度云
* @param[in]     *key 百度云KEY，
                 *imei 设备IMEI号，
                 *imsi 设备IMSI号 
                 *loc_ip 本地IP地址 
                 *scellinfo LBS信息 主基站
                 *ncellinfi LBS信息 周边基站
                 *wifiscan_info WIFI数据信息
                 *time 上报数据的时间
* @param[out]    无
* @return        pdPASS-成功  pdFAIL-失败
* @attention     无
*******************************************************************************/
static uint32_t lbs_wifiscan_http_cjson_send_to_baiduyun(   uint8_t *key,               /*百度云账户SK*/
                                                uint8_t *imei,                          /*设备IMEI*/
                                                uint8_t *imsi,                          /*设备IMSI*/
                                                uint8_t *loc_ip,                        /*本地IP地址*/
                                                uint8_t *scellinfo,                     /*LBS信息 主基站*/
                                                uint8_t *ncellinfi,                     /*LBS信息 周边基站*/
                                                uint8_t *wifiscan_info,                 /*WIFI信息*/
                                                uint8_t *time )                         /*上报数据的时间*/              
{
    uint32_t ret = pdFAIL;
    cJSON *proot = NULL, *pbody = NULL, *body_root = NULL ;
    char *post_buf = NULL;
    uint32_t scellinfoNum = 0;
    
  //  if(( key == NULL ) || ( imei == NULL ) || ( scellinfo == NULL ) || ( time == NULL ))
     if(( key == NULL ) || ( imei == NULL ) ||  ( time == NULL ))//wifi 定位主基站可以不是必须
    {
        return pdFAIL;
    }
    
    proot = cJSON_CreateObject();
    cJSON_AddStringToObject( proot,"ver","1.0" );
    cJSON_AddFalseToObject( proot,"trace" );
    cJSON_AddStringToObject( proot,"prod","test_loc_api" );
    cJSON_AddStringToObject( proot,"src","baidu_loc_api" );
    cJSON_AddStringToObject( proot,"key",(const char *)key );
    
    pbody = cJSON_CreateArray();
    cJSON_AddItemToObject(proot, "body",pbody);
    body_root = cJSON_CreateObject();
    
    if(g_LbsPositionMode == LBS_ONLY_READ || LBS_WIFI_READ == g_LbsPositionMode)//LBS 或混合定位
    {
        scellinfoNum = atoi(scellinfo);
        log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"lbs lbs_cellinfo_msg.service.mcc =  %d ",scellinfoNum);
        if(scellinfoNum)
        {
            cJSON_AddItemToObject( body_root, "bts", cJSON_CreateString( (const char *)scellinfo ));
        }
        
    }
    
    cJSON_AddItemToObject( body_root, "output", cJSON_CreateString( "JSON" ));

    if(g_LbsPositionMode == LBS_ONLY_READ || LBS_WIFI_READ == g_LbsPositionMode)//LBS 或混合定位
    {
        cJSON_AddItemToObject( body_root, "accesstype", cJSON_CreateNumber( 0 ));//移动接入网络
    } 
    if(g_LbsPositionMode == WIFI_ONLYE_READ)
    {
        cJSON_AddItemToObject( body_root, "accesstype", cJSON_CreateNumber( 1 ));//wifi接入网络
    }

    if ( wifiscan_info != NULL )
    {
        cJSON_AddItemToObject( body_root, "macs", cJSON_CreateString( (const char *)wifiscan_info ));
    }
    cJSON_AddItemToObject( body_root, "imei", cJSON_CreateString( (const char *)imei ));
    if( imsi != NULL )
    {
        cJSON_AddItemToObject( body_root, "imsi", cJSON_CreateString( (const char *)imsi ));   
    }
    if( loc_ip != NULL )
    {
       cJSON_AddItemToObject( body_root, "clientip", cJSON_CreateString( (const char *)loc_ip )); 
    }
    cJSON_AddItemToObject( body_root, "ctime", cJSON_CreateString( (const char *)time ));
    if( ncellinfi != NULL )
    {
        cJSON_AddItemToObject( body_root, "nearbts", cJSON_CreateString( (const char *)ncellinfi ));
    }
    cJSON_AddItemToObject( body_root, "cdma", cJSON_CreateNumber( 0 ));
    cJSON_AddItemToObject( body_root, "need_rgc", cJSON_CreateString( "N" ));
    cJSON_AddItemToObject( body_root, "network", cJSON_CreateString( "GPRS" ));
    cJSON_AddItemToArray( pbody, body_root );
    /*将CJSON组成的数据进行打印，同时将数据上传百度云平台*/
    post_buf = cJSON_PrintUnformatted(proot);
    //log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"cJSON_Print : %s", post_buf);



    if( lbs_wifiscan_baiduyun_http_post_msg( post_buf ) == pdPASS )
    {
        log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"lbs_wifiscan_baiduyun_http_post_msg = OK");
        ret = pdPASS;
    }
    else
    {
        log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"lbs_wifiscan_baiduyun_http_post_msg = ERR0R");
    }
    cJSON_free((void *) post_buf); 
    cJSON_Delete(proot);

    return ret;
}

/** ****************************************************************************
* @remarks       static uint32_t lbs_wifiscan_http_cjson_recv_from_baiduyun( uint8_t *data, uint32_t len )
* @brief         解析百度云接受的数据
* @param[in]     *data 数据源地址，len 数据长度
* @param[out]    无
* @return        pdPASS-成功  pdFAIL-失败
* @attention     无
*******************************************************************************/
static uint32_t lbs_wifiscan_http_cjson_recv_from_baiduyun( uint8_t *data, uint32_t len )
{
    uint32_t ret = pdFAIL;
    int32_t err_code = 0, type = 0;
    cJSON *proot = NULL, *pbody = NULL, *pindex = NULL;
    char *location = NULL, *p = NULL;
    double longitude = 0.0f, latitude = 0.0f;
    double plon = 0.0f, plat = 0.0f;
    log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"lbs_wifiscan_http_cjson_recv_from_baiduyun ",0 );
    if(( data == NULL ) || ( len == 0 ))
    {
        return pdFAIL;
    }
    //首先整体判断是否为一个json格式的数据
    log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"if(( data == NULL ) || ( len == 0 ))",0 );
    proot = cJSON_Parse( (const char *)data );
    //如果是否json格式数据
    if( proot ==NULL )
    {
        return pdFAIL;
    }
    log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"if( proot ==NULL )",0 );
    // 解析type字段数组内容
    err_code = cJSON_GetObjectItem(proot, "errcode")->valueint;    //错误会死到这个位置 没有errcode
    log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"cJSON_GetObjectItem",0 ); 
    if ( err_code == 0  )                            
    {
        log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ," if ( err_code == 0  )   ",0 );
        // 解析pbody字段数组内容
        pbody = cJSON_GetObjectItem(proot,"body");
        if( pbody != NULL )
        {
            pindex = cJSON_GetArrayItem( pbody,0 );
            type = cJSON_GetObjectItem( pindex, "type" )->valueint;
            if( type != 0 )
            {
                location = cJSON_GetObjectItem( pindex, "location" )->valuestring;
                longitude = atof((const char *)location);
                p = strchr( (const char *)location, ',');
                latitude = atof((const char *)p+1);
                bd2wgs_Exactly( latitude, longitude , &plat, &plon );
                log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"LBS coordinate position : type=%d,BD09:lon=%f,lat=%f,WGS84:lon=%f,lat=%f", 
                                    type, longitude, latitude, plon, plat ); 
                lbs_wifiscan_locating_infor.type = type;
                lbs_wifiscan_locating_infor.longitude = (uint32_t)( plon * 1000000 );
                lbs_wifiscan_locating_infor.latitude =  (uint32_t)( plat * 1000000 );;
                ret = pdPASS;
            }
        }
    }
    else 
    { 
        log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ," if ( err_code != 0  )   ",0 );
    }
    

    cJSON_Delete( proot );
    
    return ret;
}

/** ****************************************************************************
* @remarks       static uint32_t lbs_wifiscan_baiduyun_http_post_msg( char * post_data )
* @brief         百度云HTTP数据发送
* @param[in]     * post_data 发送数据源地址
* @param[out]    无
* @return        pdPASS-成功  pdFAIL-失败
* @attention     无
*******************************************************************************/
static uint32_t lbs_wifiscan_http_send_to_baiduyun( void )
{
    #define INFOR_UNIT_LEN  ( 50 )
    uint32_t ret = pdFAIL;
    uint8_t scell_infor[INFOR_UNIT_LEN] = { 0 };
    uint8_t *ncell_infor = NULL;
    uint8_t *wifi_infor = NULL;
    uint32_t timestamp = 0;
    uint8_t time_string[INFOR_UNIT_LEN] = { 0 };
    uint8_t imei[NET_MOD_IMEI_LEN+2] = { 0 };
    uint8_t imsi[NET_MOD_IMSI_LEN+2] = { 0 };
    //uint8_t locip[NET_MOD_LOC_IP_LEN+2] = { 0 };
    uint8_t lbs_num = 0, wifi_num = 0;
    uint16_t lbs_len = 0, wifi_len = 0;
    uint8_t lbs_info_num = 0;
    
    /*读取百度云KEY值，如果不存在直接退出数据发送*/
    if( lbs_wifiscan_key_infor.len == 0 )
    {
        return pdFAIL;
    }
    if( strlen( (const char *)lbs_wifiscan_key_infor.ak ) != lbs_wifiscan_key_infor.len )
    {
        return pdFAIL;
    }

    /*填充WIFI SCAN信息*****************************************************************************/
    if(g_LbsPositionMode == WIFI_ONLYE_READ || g_LbsPositionMode == LBS_WIFI_READ  )
    {
        if( wifiscan_infor_msg.mac_num > 0 )
        {
            lbs_info_num += wifiscan_infor_msg.mac_num;
            wifi_infor = (uint8_t *)gaoz_malloc_mem( INFOR_UNIT_LEN * wifiscan_infor_msg.mac_num );
            if( wifi_infor != NULL )
            {
                memset( (uint8_t *)wifi_infor, 0x00, INFOR_UNIT_LEN * wifiscan_infor_msg.mac_num );
                for ( wifi_num = 0; wifi_num < wifiscan_infor_msg.mac_num; wifi_num++ )
                {
                    sprintf( ( char *)&wifi_infor[wifi_len],"%s,%d,|", 
                                wifiscan_infor_msg.infor[wifi_num].ap_addr,
                                wifiscan_infor_msg.infor[wifi_num].ap_rssi );
                    wifi_len = strlen( (const char *)wifi_infor );
                }
                wifi_infor[wifi_len-1] = 0x00;
            }

            ret = pdPASS;
        }
    }

    /*读取LBS 主基站状态，当为0时表示不正常，直接退出*/
    if(g_LbsPositionMode == LBS_ONLY_READ || g_LbsPositionMode == LBS_WIFI_READ  )
    {
        if( lbs_cellinfo_msg.scell_num == 0 )
        {
            return pdFAIL;
        }
        lbs_info_num++;//定位信息的个数
        /*填充主基站信息******************************************************************************/
        sprintf( ( char *)scell_infor,"%d,%d,%ld,%ld,%d", 
                    lbs_cellinfo_msg.service.mcc,
                    lbs_cellinfo_msg.service.mnc,
                    lbs_cellinfo_msg.service.lac,
                    lbs_cellinfo_msg.service.cellid,
                    lbs_cellinfo_msg.service.signal );
        /*填充周边基站信息*****************************************************************************/
        
        if(lbs_info_num < 6)
        {
            lbs_cellinfo_msg.ncell_num = ((6 - lbs_info_num) < lbs_cellinfo_msg.ncell_num)?(6 - lbs_info_num):lbs_cellinfo_msg.ncell_num;
        } 
        else 
        {
            lbs_cellinfo_msg.ncell_num = 0;//6个信息已满不再添加辅助信息
        }

        if( lbs_cellinfo_msg.ncell_num > 0 )
        {
            ncell_infor = (uint8_t *)gaoz_malloc_mem( INFOR_UNIT_LEN * lbs_cellinfo_msg.ncell_num );
            if( ncell_infor != NULL )
            {
                memset( (uint8_t *)ncell_infor, 0x00, INFOR_UNIT_LEN * lbs_cellinfo_msg.ncell_num );
                for( lbs_num = 0; lbs_num < lbs_cellinfo_msg.ncell_num; lbs_num ++ ) 
                {
                    sprintf( ( char *)&ncell_infor[lbs_len],"%d,%d,%ld,%ld,%d|", 
                                lbs_cellinfo_msg.ncell[lbs_num].mcc,
                                lbs_cellinfo_msg.ncell[lbs_num].mnc,
                                lbs_cellinfo_msg.ncell[lbs_num].lac,
                                lbs_cellinfo_msg.ncell[lbs_num].cellid,
                                lbs_cellinfo_msg.ncell[lbs_num].signal );
                    lbs_len = strlen( (const char *)ncell_infor );
                }
                ncell_infor[lbs_len-1] = 0x00;
            }
        }

        ret = pdPASS;
    }

    #if 1 //LBS
    
    /*读取4G IMEI 数据*****************************************************************************/
    net_module_run_state_get( MOD_IMEI, imei );
    /*读取4G IMSI 数据*****************************************************************************/
    net_module_run_state_get( MOD_IMSI, imsi );
    /*读取系统时间**********************************************************************************/
    rtc_sys_get( RTC_TIM_TIMESTAMP, (uint32_t *)&timestamp );
    sprintf( ( char *)time_string,"%lu", timestamp );
    /*向百度云POST信息，获取经纬度坐标信息************************************************************/
    ret = lbs_wifiscan_http_cjson_send_to_baiduyun( (uint8_t *)lbs_wifiscan_key_infor.ak, 
                                                    (uint8_t *)imei, 
                                                    (uint8_t *)imsi,
                                                    (uint8_t *)NULL,
                                                    (uint8_t *)scell_infor,
                                                    (uint8_t *)ncell_infor,
                                                    (uint8_t *)wifi_infor,
                                                    (uint8_t *)time_string);
   
    #endif
    /*释放动态申请得系统空间*/
    if( ncell_infor != NULL )
    {
        gaoz_free_mem( (void *)ncell_infor );
    }
    if( wifi_infor != NULL )
    {
        gaoz_free_mem( (void *)wifi_infor );
    }

    if(ret == pdPASS)
    { 
        log_debug_printf( DEBUG_MODE, LBS_MAN_NAME, "lbs info get sucess  \r\n",0);
    }
    else 
    { 
        log_debug_printf( DEBUG_MODE, LBS_MAN_NAME, "lbs info get fail  \r\n",0);
    }

    return ret;
}

/** ****************************************************************************
* @remarks       static uint32_t lbs_wifiscan_infor_read( uint32_t mode )
* @brief         LBS WIFISCAN 辅助定位数据管理处理任务
* @param[in]     mode 读取数据的模式
* @param[out]    无
* @return        pdPASS-成功  pdFAIL-失败
* @attention     无
*******************************************************************************/
static uint32_t lbs_wifiscan_infor_read( uint32_t mode )
{
    #define LBS_WIFISCAN_WAIT_TIMEOUT ( 6*5000 )/* 2024年7月17日19:39:38 修改为最大30S等待 */
    uint32_t ret = pdFAIL;
    uint8_t net_run_st = 0, ble_power_st = 0;

    g_LbsPositionMode = mode; 
    /*将寄存器清空*/
    memset( (uint8_t *)&lbs_wifiscan_locating_infor, 0x00, sizeof( lbs_wifiscan_locating_infor_t ) );
    /*读取百度云KEY值，如果不存在直接退出数据发送*/
    if( lbs_wifiscan_key_infor.len == 0 )
    {
        g_LbsStata = LBS_STATA_IDLE;
        return pdFAIL;
    }
    /*获取网络状态，网络异常时直接退出*/
    net_module_run_state_get( MOD_STATE ,(uint8_t *)&net_run_st );
    if( net_run_st != MODULE_NET_OPEN )
    {
        g_LbsStata = LBS_STATA_IDLE;
        return pdFAIL;
    }
    if( mode == LBS_ONLY_READ )
    {
        /*网络正常是，调用610接口读取基站信息，等待应答结果*/
        fibo_getCellInfo_ex( lbs_get_cellinfo_ex_cb, 0 );
        if( lbs_wifscan_read_msg_semaphore_get( LBS_WIFISCAN_WAIT_TIMEOUT ) == pdPASS )
        {
            ret = pdPASS;
        }
    }
    else if( mode == LBS_WIFI_READ )
    {
        /*网络正常是，调用610接口读取基站信息，等待应答结果*/
        fibo_getCellInfo_ex( lbs_get_cellinfo_ex_cb, 0 );
        if( lbs_wifscan_read_msg_semaphore_get( LBS_WIFISCAN_WAIT_TIMEOUT ) == pdPASS )
        {
            ret = pdPASS;
        }
        /*网络读取成功时，开始读取WIFI AP信息，如果没有基站信息基本存在WIFI AP信息也无法正常使用，所以优先判断基站信息*/
        if( ret == pdPASS )
        {
            /*判断当前蓝牙是否处于连接状态，如果处于连接状态时则打开WIFI SCAN功能*/
            if( ble_drive_gatt_connect_get() != BLE_GATT_CONNECT )
            {
                if( ble_drive_gatt_connect_get() == BLE_GATT_BROAD_OK )
                {
                    ble_drive_data_close( "CLOSE-NOW" );        /*立即关闭蓝牙功能*/
                    log_debug_send(DEBUG_MODE,LBS_MAN_NAME ,"WIFISCAN is ready to turn on, immediately turn off BLE\r\n",0);
                    gaoz_task_sleep( 3000 );                    /*延迟1S钟等待BLE底层驱动稳定*/ 
                    ble_power_st = 0x01;
                }
                if( fibo_wifiscan_on() >= 0 )                   /*打开WIFISCAN 功能，启动数据读取*/
                {
                    log_debug_send(DEBUG_MODE,LBS_MAN_NAME ,"fibo_wifiscan_on() == pdPASS\r\n",0);
                   
                    fibo_wifiscan( wifiscan_refponse_cb );
                    if( lbs_wifscan_read_msg_semaphore_get( LBS_WIFISCAN_WAIT_TIMEOUT ) == pdPASS )
                    {
                        ret = pdPASS;
                    } 
                }
                else 
                {
                    log_debug_send(DEBUG_MODE,LBS_MAN_NAME ,"fibo_wifiscan_on() == pdFail\r\n",0);
                }
                if( ble_power_st == 0x01 )
                {
                    ble_drive_gatt_connect_set( BLE_GATT_OPEN ); /*重新启动BLE服务*/
                    log_debug_send(DEBUG_MODE,LBS_MAN_NAME ,"WIFISCAN complete, restart BLE\r\n",0);
                 }
            }
        }
    }
    else if( mode == WIFI_ONLYE_READ )
    {
        if( ble_drive_gatt_connect_get() != BLE_GATT_CONNECT )
        {
            if( ble_drive_gatt_connect_get() == BLE_GATT_BROAD_OK )
            {
                ble_drive_data_close( "CLOSE-NOW" );        /*立即关闭蓝牙功能*/
                log_debug_send(DEBUG_MODE,LBS_MAN_NAME ,"WIFISCAN is ready to turn on, immediately turn off BLE\r\n",0);
                gaoz_task_sleep( 1000 );                    /*延迟1S钟等待BLE底层驱动稳定*/ 
                ble_power_st = 0x01;
            }
            if( fibo_wifiscan_on() >= 0 )                   /*打开WIFISCAN 功能，启动数据读取*/
            {
                fibo_wifiscan( wifiscan_refponse_cb );
                if( lbs_wifscan_read_msg_semaphore_get( LBS_WIFISCAN_WAIT_TIMEOUT ) == pdPASS )
                {
                    ret = pdPASS;
                }
            }
            if( ble_power_st == 0x01 )
            {
                ble_drive_gatt_connect_set( BLE_GATT_OPEN ); /*重新启动BLE服务*/
                log_debug_send(DEBUG_MODE,LBS_MAN_NAME ,"WIFISCAN complete, restart BLE\r\n",0);
            }
        }
        // if( ret == pdPASS )
        // {
        //     /*网络正常是，调用610接口读取基站信息，等待应答结果*/
        //     fibo_getCellInfo_ex( lbs_get_cellinfo_ex_cb, 0 );
        //     if( lbs_wifscan_read_msg_semaphore_get( LBS_WIFISCAN_WAIT_TIMEOUT ) == pdPASS )
        //     {
        //         ret = pdPASS;
        //     }
        //     else
        //     {
        //         ret = pdFAIL;
        //     }
        // }
    }
    else
    {
        ret = pdFAIL;
    }
    /*基站信息 WIFI信息获取成功后，向百度云发送HTTP请求数据*/
    if( ret == pdPASS )
    {
        ret = lbs_wifiscan_http_send_to_baiduyun();
    }

    g_LbsStata = LBS_STATA_IDLE;
    
    return ret;
}

/** ****************************************************************************
* @remarks       uint32_t lbs_wifiscan_coordinate_position_read( uint32_t mode, uint32_t time, lbs_wifiscan_recv_fun_t fun )
* @brief         读取LBS 辅助定位信息
* @param[in]     mode 读取数据模式，time 周期时间（预留），fun 回调函数
* @param[out]    无
* @return        pdPASS-成功，pdFAIL-失败
* @attention     无
*******************************************************************************/
uint32_t lbs_wifiscan_coordinate_position_read( uint32_t mode, uint32_t time, lbs_wifiscan_recv_fun_t fun )
{
    uint32_t ret = pdFAIL;
    lbs_wifscan_msg_typedef msg = { 0 };

    if(( mode == 0 ) || ( mode > WIFI_ONLYE_READ ))
    {
        return pdFAIL;
    }

    if(g_LbsStata == LBS_STATA_IDLE)
    {
        msg.mode = mode;
        msg.time = time;
        msg.fun = fun;
        ret = lbs_wifscan_msg_queue_set( &msg );
        if(ret == pdPASS)
        {
            log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"start get lbs info g_LbsStata == LBS_STATA_IDLE lbs_wifscan_msg_queue_set type =  %d ----start get lbs info---- ",mode);
           g_LbsStata = LBS_STATA_BUSY; 
        }
    }
    else 
    {
        log_debug_printf(DEBUG_MODE,LBS_MAN_NAME ,"start get lbs info g_LbsStata == LBS_STATA_BUSY lbs_wifscan_msg_queue_set type =  pdFail ----s get lbs info pdfail---- ",0);
            
    }

    return ret;
}

/** ****************************************************************************
* @remarks       uint32_t lbs_wifiscan_key_save_flash_write( lbs_wifiscan_key_infor_t *key_cfg )
* @brief         保存LBS KEY 配置参数到外部FLASH中
* @param[in]     *key_cfg 保存数据源地址
* @param[out]    无
* @return        pdPASS 成功 pdFAIL 失败
* @attention     无
*******************************************************************************/
uint32_t lbs_wifiscan_key_save_flash_write( uint8_t *data, uint16_t len )
{
    uint32_t ret = pdFAIL;
    
    if(( len <= LBS_WIFISCAN_KEY_LEN ) && ( data != NULL ))
    {
        ret = save_lbs_key_write_to_flash( (uint8_t *)data, len );
        if( ret == pdPASS )
        {
            lbs_wifiscan_key_infor.len = len;
            memcpy( (uint8_t *)lbs_wifiscan_key_infor.ak, (uint8_t *)data, lbs_wifiscan_key_infor.len );
        }
    }

    return ret;
}

/** ****************************************************************************
* @remarks       uint32_t lbs_wifiscan_key_save_flash_write( lbs_wifiscan_key_infor_t *key_cfg )
* @brief         保存LBS KEY 配置参数到外部FLASH中
* @param[in]     *key_cfg 保存数据源地址
* @param[out]    无
* @return        pdPASS 成功 pdFAIL 失败
* @attention     无
*******************************************************************************/
uint8_t lbs_wifiscan_key_save_flash_read( uint8_t *data )
{
    if( data == NULL )
    {
        return 0;
    }
    memcpy((uint8_t *)data, (uint8_t *)lbs_wifiscan_key_infor.ak, lbs_wifiscan_key_infor.len );

    return lbs_wifiscan_key_infor.len;
}

/** ****************************************************************************
* @remarks       uint32_t lbs_wifiscan_key_save_flash_read( lbs_wifiscan_key_infor_t *key_cfg )
* @brief         读取 LBS KEY 配置参数
* @param[in]     无
* @param[out]    *key_cfg 读取数据目标地址
* @return        pdPASS 成功 pdFAIL 失败
* @attention     无
*******************************************************************************/
void lbs_wifiscan_key_save_flash_clear( void )
{
    lbs_wifiscan_key_infor.len = 0x00;
    memset( (uint8_t *)lbs_wifiscan_key_infor.ak, 0x00, LBS_WIFISCAN_KEY_LEN );
    save_lbs_key_flash_clear();
}

/** ****************************************************************************
* @remarks       static void lbs_wifiscan_handle_task( void * pvParameters )
* @brief         LBS WIFISCAN 辅助定位数据管理处理任务
* @param[in]     * pvParameters 任务参数
* @param[out]    无
* @return        无
* @attention     无
*******************************************************************************/
static void lbs_wifiscan_handle_task( void * pvParameters )
{
    ( void ) pvParameters;
    #define LBS_WIFISCAN_MSG_QUEUE_WAIT_TIME    ( 1000 )
    lbs_wifscan_msg_typedef lbs_msg = { 0 };
    g_LbsStata = LBS_STATA_IDLE;
    mon_reg_task_dog( 60 * GAOZ_TICK_PERIOD_S ,(uint8_t *)LBS_MAN_NAME , TASK_SEM_YES ); /*注册任务看门狗*/
    log_debug_send(DEBUG_MODE,LBS_MAN_NAME ,"LBS/wifiscan management task started successfully\r\n",0);
    for( ;; )
    {
        mon_reset_task_dog();
        if( lbs_wifscan_msg_queue_get( (lbs_wifscan_msg_typedef *)&lbs_msg , LBS_WIFISCAN_MSG_QUEUE_WAIT_TIME ) == pdPASS )
        {
            if( lbs_wifiscan_infor_read( lbs_msg.mode ) == pdPASS )
            {
               
                if( lbs_msg.fun != NULL )
                {
                    lbs_msg.fun( lbs_wifiscan_locating_infor.type, lbs_wifiscan_locating_infor.latitude, lbs_wifiscan_locating_infor.longitude );
                }
            }
            else
            {
                if( lbs_msg.fun != NULL )   /*数据读取失败，返回错误值*/
                {
                    lbs_msg.fun( 0, 0, 0 );
                }
            }
        }
    }
}

